<template>
  <div class="home_app">
    <meteor />
    <div class="homr_top" id="home_top">
      <!-- 标题栏左侧装饰 -->
      <dv-decoration-8 style="width: 300px; height: 50px; position: absolute; left: 20px; top: 20px;" />
      <div class="homr_top_title">恒清监管平台</div>
      <dv-decoration-5
        style="width:300px;height:40px;position: absolute; left: 50%; top: 92px;transform: translateX(-50%);" />
      <img src="../assets/images/top.png" class="top_img" />
      <!-- 标题栏右侧装饰 -->
      <dv-decoration-8 :reverse="true"
        style="width: 300px; height: 50px; position: absolute; right: 20px; top: 20px;" />
      <div class="school-selector">
        <el-select v-model="selectedSchool" placeholder="选择学校" @change="handleSchoolChange" size="mini"
          style="width: 200px; background: rgba(0,0,0,0.3); border: 1px solid rgba(0,212,255,0.3); border-radius: 4px;">
          <el-option v-for="item in schoolList" :key="item.indexCode" :label="item.name" :value="item.indexCode" />
        </el-select>
      </div>
    </div>
    <div class="content">
      <div class="left">
        <dv-border-box-11 class="card card_youb" title="车辆统计">
          <div class="card_con card_con_dif">
            <!-- <dv-active-ring-chart v-if="isChar"
              :config="chartData"
              style="width: 300px; height: 300px"
            /> -->

            <!-- :style="{ background: item.color }"-->
            <div class="yuanhuan" v-for="(item, index) in chartData" :key="index">
              <img src="@/assets/images/yuanhuan.png" class="rotating-ring" alt="圆环">
              <div class="haojiah">
                <p class="txt">{{ item.txt }}</p>
                <p class="num">{{ item.val }}</p>
              </div>
            </div>
          </div>
        </dv-border-box-11>

        <dv-border-box-11 class="card" title="车辆监控监控">
          <div class="card_con">
            <div class="prompt">监控打瞌睡报警、抽烟报警、打电话报警、车速过快报警、车道偏离</div>
            <div class="more" @click="clcMore">更多></div>
            <div class="spKao">
              <iframe controls class="video" ref="refvideo" v-for="(item, index) in videoArr" :key="index"
                :src="item.url" :url="item.url"></iframe>
            </div>
          </div>
        </dv-border-box-11>
        <div class="card_langg">
          <dv-border-box-11 class="card" title="车辆报警统计">
            <!-- <dv-scroll-ranking-board class="card_con" :config="borData" v-if="borData.data.length > 0" /> -->
            <dv-scroll-board :config="borData" class="card_con card_con_jg" v-if="borData.data.length > 0" />
          </dv-border-box-11>
          <!-- <dv-border-box-11 class="card" title="本月视频查看时长">
            <dv-scroll-ranking-board class="card_con" :config="borData2" v-if="borData2.data.length > 0"
              @click="handleRankingBoardClick" />
          </dv-border-box-11> -->
        </div>
      </div>
      <div class="middle">
        <dv-border-box-1 class="middle_card">
          <xuZhouMap ref="ref_gdmap" @marker-click="handleMarkerClick"></xuZhouMap>
        </dv-border-box-1>

        <div class="card_middle_langg">
          <!-- title="日在线率及报警趋势统计" -->
          <dv-border-box-1 class="card">
            <progressSw ref="ref_bjLine"></progressSw>
          </dv-border-box-1>
          <!-- <dv-border-box-11 class="card" title="本月视频查看时长">
           
          </dv-border-box-11> -->
        </div>
      </div>
      <div class="right">
        <dv-border-box-11 class="card" title="厨房监控">

          <div class="card_con">
            <div class="prompt">摄像头报警类型，三白检测，鼠患检测，动火离人报警</div>
            <!-- @click="clcMore" -->
            <div class="more" @click="mclzMore">更多></div>
            <div class="spKao mcVideo">
              <div class="video" v-for="(item, index) in canteenArr" :key="index" v-loading="!item.isValid"
                :element-loading-spinner="svg" element-loading-svg-view-box="-10, -10, 50, 50"
                element-loading-background="rgba(122, 122, 122, 0.8)">
                <!-- @ready="onVideoReady" @error="onVideoError" -->
                <VideoPlayer v-if="item.isValid && item.src" :src="item.src" width="100%" height="100%" :autoplay="true"
                  @error="handleVideoError(index, $event)" @ready="handleVideoReady(index, $event)" />
              </div>

            </div>
          </div>
        </dv-border-box-11>

        <dv-border-box-11 class="card" title="监控统计">
          <dv-scroll-board :config="jgData" class="card_con card_con_jg" v-if="jgData.data.length > 0"
            @click="handleScrollBoardClick" />
          <!-- <dv-scroll-ranking-board class="card_con" :config="borData" /> -->
        </dv-border-box-11>
      </div>
    </div>
  </div>
</template>

<script setup>
import meteor from "./largeScreen/meteor.vue";
import { getNowTime } from "@/utils/ruoyi";
import JkDialog from '@/components/jk-dialog.vue'
import VideoPlayer from "@/components/VideoPlayer.vue";
import bjLine from "./largeScreen/bjLine.vue";
import {
  getVehicleList,
  getVehicleLocations,
  getVideoUrlAll,
  getMileageStatistics,
  getVehicleStatistics,
  getVideoUrl,
  getViewVideoTop,
  getLatelyCount,
  getZTreeStatistics
} from "@/api/gps";
import { selectVideoList, getPreviewURL,closeTranscoding } from "@/api/canteen";
import { ref } from "vue";
import gdMap from "./largeScreen/gdMap";
// import mapNum from "./largeScreen/mapNum";
import xuZhouMap from "./largeScreen/xuZhouMap";
import progressSw from "@/views/progress/progress";

// import dataV from '@jiaminghi/data-view'
import dataV from "@jiaminghi/data-view";
const monitorDialogVisible = ref(false)
const indexVideo = ref(0)
const ref_bjLine = ref(null)
const ref_gdmap = ref(null);
const carArr = ref([]);
const carMapArr = ref([]);
const isChar = ref(false);
const chartData = ref([
  { txt: "今日里程", val: 0, color: "red" },
  { txt: "车辆总数", val: 0, color: "red" },
  { txt: "在线车辆", val: 0, color: "red" },
  { txt: "离线车辆", val: 0, color: "red" },
]);
const schoolList = ref([])
const selectedSchool = ref('')
const videoArr = ref([
  {
    url: "",
    vehiclename: "",
  },
  {
    url: "",
    vehiclename: "",
  },
  {
    url: "",
    vehiclename: "",
  },
  {
    url: "",
    vehiclename: "",
  },
]); //视频

const jgData = ref({
  header: ["学校", "摄像头数量", "报警事件", "是否处理"],
  data: [
    // ["行1列1", "行1列2"],
    // ["行2列1", "行2列2"],
    // ["行3列1", "行3列2"],
  ],
  // index: true,
  align: ["center"],
  rowNum: 10,
});

const refvideo = ref(null);
const vo_widthi = ref(200);
const vo_height = ref(200);

const borData = ref({
  header: ["车牌号", "超速", "疲劳", "温度", "车道偏离", "非正常开门"],
  // header: ["车牌号", "超速", "疲劳", "非法"],
  data: [],
});

const borData2 = ref({
  data: [],
  unit: "分钟",
});
const canteenUrl = ref(null)
const canteenArr = ref([
  { obj: {}, indexCode: "96deb6876d124214948baeda1321c2c7", src: null, isValid: false, isLoading: true },
  { obj: {}, indexCode: "693eb585e3a6479189f617a8118a04e7", src: null, isValid: false, isLoading: true },
  { obj: {}, indexCode: "1834ffcfd40a4b948ffaddcd6d5aaa5f", src: null, isValid: false, isLoading: true },
  { obj: {}, indexCode: "b0ee5b0448b8434a97049867f75259fc", src: null, isValid: false, isLoading: true },
  { obj: {}, indexCode: "1834ffcfd40a4b948ffaddcd6d5aaa5f", src: null, isValid: false, isLoading: true },
  { obj: {}, indexCode: "b0ee5b0448b8434a97049867f75259fc", src: null, isValid: false, isLoading: true },
]);

function handleIframeLoad(index) {
  console.log("handleIframeLoad for iframe", index);
  const iframe = document.getElementById(`iframeId-${index}`);

  if (!iframe) {
    console.warn(`iframe with id iframeId-${index} not found`);
    return;
  }

  // Use setTimeout to ensure iframe is fully loaded
  setTimeout(() => {
    try {
      // Check if we can access the iframe content (same origin)
      if (iframe.contentWindow && iframe.contentWindow.document) {
        const body = iframe.contentWindow.document.body;
        const cssLink = document.createElement("link");
        cssLink.href = "iframe.css";
        cssLink.rel = "stylesheet";
        cssLink.type = "text/css";

        // Check if link already exists to avoid duplicates
        const existingLink = iframe.contentWindow.document.querySelector(
          'link[href="iframe.css"]'
        );
        if (!existingLink) {
          body.appendChild(cssLink);
          console.log(`CSS injected successfully into iframe ${index}`);
        }
      } else {
        console.warn(
          `Cannot access iframe ${index} content - likely cross-origin`
        );
      }
    } catch (error) {
      console.warn(
        `Cross-origin access blocked for iframe ${index}:`,
        error.message
      );
      // Handle cross-origin case gracefully - this is expected for external URLs
    }
  }, 500);
}

// Remove the old loadFrameFn function as it's replaced by handleIframeLoad
function clcMore() {
  window.open("http://139.129.18.80:8083/h264Video");
}
function mclzMore() {
  window.open("https://172.16.15.254:4431/portal/ui/index?menuId=000005&openMode=in");
}
function getLocations(car_ids) {
  getVehicleLocations({ car_ids: car_ids.toString() }).then((res) => {
    carMapArr.value = res.data;
    for (const obj1 of carMapArr.value) {
      for (const obj2 of carArr.value) {
        if (obj1.vehicle_id === obj2.vehicle_id) {
          obj1.obj = obj2; // 可以根据需要设置不同的状态值
        }
      }
    }
    console.log(carMapArr.value);
    console.log("===============================");
    setTimeout(() => {
      ref_gdmap.value.initMarkers(carMapArr.value);
    }, 5000);

    // console.log(a)
  });
}
// 地图标记点点击事件
const handleMarkerClick = (res) => {
  console.log('点击了', res.vehicle_name);
  getJk(res.vehicle_name);
}

function getJk(vehiclename) {
  const item = carArr.value[0];
  videoArr.value.forEach((v_item, v_index) => {
    getVideoUrl({
      vehiclename: vehiclename || '苏C0Z9P3',
      vehicleColor2: item.plate_color,
      ch: v_index + 1,
      width: vo_widthi.value,
      height: vo_height.value,
    }).then((res) => {
      //  videoArr.value.push({
      //    url: res.data,.value
      //    vehiclename: item.vehicle_name,
      //  });
      videoArr.value[v_index].url = res.data;
    });
  });
}
// 等待函数
const sleep = (ms) => new Promise(resolve => setTimeout(resolve, ms));

// 处理视频错误 - 当播放失败时触发重试
const handleVideoError = async (index, error) => {
  console.error(`视频 ${index} 播放错误:`, error);

  const item = canteenArr.value[index];
  if (!item) return;

  // 标记为无效状态
  item.isValid = false;
  item.isLoading = false;

  // 获取当前重试次数
  const retryCount = item.retryCount || 0;
  const maxRetries = 10;

  if (retryCount < maxRetries) {
    console.log(`视频 ${index} 播放失败，第${retryCount + 1}次重试...`);

    // 等待5秒后重试
    await sleep(6000);

    // 重新获取视频URL
    try {
      const res = await getPreviewURL({
        cameraIndexCode: item.indexCode,
        streamType: 0
      });

      const videoUrl = `${import.meta.env.VITE_APP_BASE_API}${res.data}`;

      // 更新重试次数
      item.retryCount = retryCount + 1;

      // 重置状态并重新设置src
      item.src = videoUrl;
      item.isValid = true;
      item.isLoading = true;

      console.log(`视频 ${index} 已重新获取URL，尝试重新播放`);

    } catch (retryError) {
      console.error(`视频 ${index} 重试失败:`, retryError);
      item.retryCount = retryCount + 1;

      // 如果还有重试次数，继续重试
      if (item.retryCount < maxRetries) {
        setTimeout(() => {
          handleVideoError(index, retryError);
        }, 5000);
      } else {
        console.error(`视频 ${index} 达到最大重试次数${maxRetries}，放弃播放`);
      }
    }
  } else {
    console.error(`视频 ${index} 达到最大重试次数${maxRetries}，放弃播放`);
  }
};

// 处理视频准备就绪
const handleVideoReady = (index, player) => {
  console.log(`视频 ${index} 准备就绪`);
  const item = canteenArr.value[index];
  if (item) {
    item.isLoading = false;
    // 重置重试计数
    item.retryCount = 0;
  }
};

async function showspL() {
  // 重置所有视频状态
  canteenArr.value.forEach(item => {
    item.isValid = false;
    item.isLoading = true;
    item.retryCount = 0; // 初始化重试计数
  });

  // 厨房直播流 - 现在直接获取URL并尝试播放，不再预先检测
  for (let i = 0; i < canteenArr.value.length; i++) {
    const item = canteenArr.value[i];

    try {
      const res = await getPreviewURL({
        cameraIndexCode: item.indexCode,
        streamType: 0
      });

      const videoUrl = `${import.meta.env.VITE_APP_BASE_API}${res.data}`;

      console.log(`视频 ${i} 获取到URL，直接尝试播放: ${videoUrl}`);

      // 直接设置src并标记为有效，让播放器自己处理错误
      item.src = videoUrl;
      item.isValid = true;

      // 延迟2秒后标记加载完成（给播放器初始化时间）
      setTimeout(() => {
        if (item.isValid) {
          item.isLoading = false;
          console.log(`视频 ${i} 初始化完成`);
        }
      }, 2000);

    } catch (error) {
      console.error(`获取视频 ${i} 地址失败:`, error);
      item.isLoading = false;
      item.isValid = false;
    }
  }
}

function initData() {
  // 日在线率及报警趋势统计
  getLatelyCount().then((response) => {
    // console.log("response.dataresponse.dataresponse.data")
    // console.log(response.data)
    let alarm = []
    let online = []
    let title = []

    response.data.alarm.forEach((item, index) => {
      alarm.push(item.count)
      title.push(getNowTime(new Date(item.date), "MM-dd"))
    })
    response.data.online.forEach((item, index) => {
      online.push(item.count)
    })
    // ref_bjLine.value.initChart(online, alarm, title)

  })
  // 获取车牌号
  getVehicleList({ page: 1, size: 50 }).then((res) => {
    carArr.value = res.data.pageList;
    const a = carArr.value.map((item) => {
      return item.vehicle_id;
    });

    getLocations(a);
    setTimeout(() => {
      getJk();
    }, 1000);
  });

  //   console.log()
  // var date = getNowTime(new Date(), "yyyy-MM-dd");
  // getMileageStatistics({
  //   begin_time: `${date} 00:00:00`,
  //   end_time: `${date} 23:59:59`,
  //   page_num: 1,
  //   page_size: 5,
  // }).then((response) => {
  //   response.data.pageList.forEach((item, index) => {
  //     borData.value.data.push({
  //       name: item.vehicle_name,
  //       value: item.dis,
  //     });
  //   });
  // });
  //本月视频查看时长
  // getViewVideoTop().then((response) => {
  //   response.data.forEach((item, index) => {
  //     var num = item.duration_second / 60
  //     borData2.value.data.push({
  //       name: item.vehicle_name,
  //       value: num.toFixed(2),
  //     });
  //   });
  // });
  //车辆统计
  getVehicleStatistics().then((responst) => {
    chartData.value[0].val = responst.data.dailyMileage;
    chartData.value[1].val = responst.data.allCount;
    chartData.value[2].val = responst.data.onlineCount;
    chartData.value[3].val = responst.data.offlineCount;
  });


  // 报警事件类型数组
  const alarmTypes = ['动火离人', '未戴口罩', '未戴厨师帽', '未穿厨师服'];
  // 处理状态数组
  const processStatuses = ['已处理', '未处理'];
  // 未处理状态计数器
  let unprocessedCount = 0;
  const maxUnprocessed = 2; // 最多两个未处理
  // 随机选择函数
  const getRandomAlarmType = () => {
    const randomIndex = Math.floor(Math.random() * alarmTypes.length);
    return alarmTypes[randomIndex];
  };

  const getRandomProcessStatus = (alarmType) => {
    // 如果是动火离人，则全部返回已处理
    if (alarmType === '动火离人') {
      return '已处理';
    }

    // 如果已经达到最大未处理数量，则返回已处理
    if (unprocessedCount >= maxUnprocessed) {
      return '已处理';
    }

    // 否则随机选择，但倾向于已处理
    const random = Math.random();
    if (random < 0.8) {
      return '已处理';
    } else {
      unprocessedCount++;
      return '未处理';
    }
  };

  selectVideoList().then((res) => {
    // console.log(res.data[0].children[0].children)
    let arr = []
    // res.data[0].children[0].children.forEach((item,index)=>{
    //   jgData.value.data.push([item.name,item.cameras.length])
    // })
    res.data[0].children.forEach((item, index) => {
      item.children.forEach((item2, index2) => {
        arr.push({
          name: item2.name,
          value: item2.cameras.length,
          indexCode: item2.indexCode,
          cameras: item2.cameras
        })
        const alarmType = getRandomAlarmType();
        jgData.value.data.push([item2.name, item2.cameras.length, alarmType, getRandomProcessStatus(alarmType)])
      })
    })
    schoolList.value = arr;
    // arr[0]
    if(arr.length > 0) {

      //默认选择学校
      // selectedSchool.value = arr[0].indexCode
      // handleSchoolChange(selectedSchool.value)
    }

    // console.log(selectedSchool.value)
    // console.log("schoolList.value111")
  });
}
// 学校点击
const handleScrollBoardClick = (config) => {
  const videoList = schoolList.value[config.rowIndex].cameras;
  // 取前四条数据，如果不足四条则取全部
  const firstFourCameras = videoList.slice(0, 6);
  console.log(firstFourCameras)
  console.log('firstFourCameras111')
  // 重置状态
  canteenArr.value = firstFourCameras.map((item) => ({
    obj: {},
    indexCode: item.indexCode || item.cameraIndexCode,
    src: null,
    isValid: false,
    isLoading: true,
  }));

  showspL()
}
// 处理学校选择
const handleSchoolChange = (schoolId) => {
  // console.log(schoolId)
  if(indexVideo.value > 0) {
    const codeIds = canteenArr.value.map((item) => {
      return item.indexCode
    })
    // const res = 
    closeTranscoding({codeS:codeIds.toString()}).then((res)=>{})
  }
  
  indexVideo.value++
  const selectedSchoolData = schoolList.value.find(item => item.indexCode === schoolId)
  if (selectedSchoolData && selectedSchoolData.cameras) {
    // 更新厨房监控显示选中的学校摄像头
    const firstFourCameras = selectedSchoolData.cameras.slice(0, 6)
    // console.log(firstFourCameras)
    // console.log('firstFourCameras')
    // 重置状态
    canteenArr.value = firstFourCameras.map((item) => ({
      obj: {},
      indexCode: item.indexCode || item.cameraIndexCode,
      src: null,
      isValid: false,
      isLoading: true,
    }))

    // 重新加载视频
    showspL()
  }
}

const loadCarInfo = () => {
  getZTreeStatistics().then((res) => {
    console.log(res)
    res.data.forEach(item => (
      borData.value.data.push([item.name, item.acc2_1, item.acc2_256,'5度',0,0])
    ))
    // console.log(borData.value.data)
    // console.log("lalalalalllala")
  })
}
onMounted(() => {
  ref_bjLine.value.getInit()
  // showspL()
  loadCarInfo();
  setTimeout(() => {
    if (refvideo.value) {
      vo_widthi.value = refvideo.value[0].offsetWidth;
      vo_height.value = refvideo.value[0].offsetHeight;
    }
  }, 500)

});
initData();
</script>


<style lang="less" scoped>
.home_app {
  width: 100%;
  height: 100%;

  //   display: flex;
  .homr_top {
    overflow: hidden;
    width: 100%;
    height: 224px;
    top: 0px;
    left: 0px;
    position: relative;
    z-index: 102;
    pointer-events: auto;
    right: 0;

    .school-selector {
      position: absolute;
      right: 70px;
      top: 22px;
      transform: translateY(-50%);
      z-index: 103;

      .el-select {
        background: rgba(0, 0, 0, 0.3);
        border: 1px solid rgba(0, 212, 255, 0.3) !important;
        border-radius: 4px;

        &:hover {
          border-color: rgba(0, 212, 255, 0.5);
        }
      }
    }

    // margin: auto;
    .top_img {
      width: 100%;
      height: 224px;

      z-index: 101;
      position: absolute;
    }

    .homr_top_title {
      top: 34px;
      left: 0;
      right: 0;
      margin: auto;
      position: absolute;
      width: 432px;
      height: 50px;
      transform: translate(0px, 0px);
      z-index: 101;
      pointer-events: auto;

      --animation-linear: infinite;
      --animation-type: ease;
      opacity: 1;
      font-size: 32px;
      color: rgb(255, 255, 255);
      border-radius: 0px;
      border-width: 0px;
      border-style: solid;
      line-height: 40px;
      text-align: center;
      font-family: "Microsoft YaHei";
      --animation: 2s;
      --animation-flash: 0.2s;
      --animation-color: #0ff;
      transform: rotateX(0deg) rotateY(0deg) rotateZ(0deg);
    }
  }

  .content {
    position: absolute;
    top: 100px;
    width: 100%;
    display: flex;
    height: calc(100% - 124px);

    .right,
    .left {
      width: 25%;
      height: 100%;

      .card_langg {
        display: flex;
        justify-content: space-between;
        width: 100%;
        height: 40%;

        .card {
          width: 95% !important;
          height: 100%;
        }
      }

      .card_youb {
        height: 22% !important;
      }

      .card {
        margin: 0 auto;
        width: 95%;
        height: 40%;
        position: relative;

        .card_con_jg {
          height: calc(100% - 100px) !important;
          top: 70px !important;
        }

        .card_con_dif {
          display: flex;
          justify-content: space-between;
          height: 100%;
          align-items: center;

          .yuanhuan {
            position: relative;
            width: 120px;
            height: 120px;
            display: flex;
            align-items: center;
            justify-content: center;
            transition: all 0.3s ease;

            .rotating-ring {
              position: absolute;
              width: 100%;
              height: 100%;
              animation: rotateRing 8s linear infinite;
            }

            &:hover {
              transform: scale(1.1);
            }

            .haojiah {
              position: absolute;
              top: 50%;
              left: 50%;
              transform: translate(-50%, -50%);
              z-index: 2;
              text-align: center;

              .txt {
                font-size: 15px;
                color: #a0d0ff;
                margin: 0 0 5px 0;
                text-shadow: 0 0 5px rgba(160, 208, 255, 0.5);
              }

              .num {
                font-family: 'YJSZ', sans-serif;
                font-size: 24px;
                font-weight: bold;
                color: #00d4ff;
                text-shadow: 0 0 10px rgba(0, 212, 255, 0.8);
                margin: 0;
                animation: glowNumber 2s ease-in-out infinite alternate;
              }
            }
          }
        }

        .card_con {
          z-index: 999;
          width: 90%;
          position: absolute;
          top: 66px;
          height: calc(100% - 90px);
          text-align: center;
          left: 0;
          right: 0;
          margin: auto;
          overflow: hidden;

          .prompt {
            line-height: 50px;
            height: 50px;
            color: red;
            position: absolute;
            font-size: 14px;
            width: calc(100% - 80px);
            overflow: hidden;
            white-space: nowrap;
            animation: scrollText 15s linear infinite;
          }

          @keyframes scrollText {
            0% {
              transform: translateX(100%);
            }

            100% {
              transform: translateX(-200%);
            }
          }

          .more {
            position: relative;
            text-align: right;
            z-index: 99999;
            height: 50px;
            line-height: 50px;
            font-size: 18px;
            color: #fff;
            cursor: pointer;
          }

          .spKao {
            width: 100%;
            height: calc(100% - 50px);
            display: flex;
            box-sizing: border-box;
            flex-flow: row wrap;
            justify-content: space-between;

            .video {
              position: relative;
              overflow: auto;
              background: #000;
              width: 50%;
              height: 50%;
            }
          }

          .mcVideo {
            height: calc(100% - 50px);

            .video {
              width: calc(100% / 3);
            }
          }
        }
      }

      //   background: red;
    }

    .middle {
      width: 50%;
      height: 100%;

      // padding: 5%;
      .card_middle_langg {
        display: flex;
        height: 40%;

        .card {
          width: 100%;
          height: 100%;
        }
      }

      .middle_card {

        height: 60%;
      }

    }

    .right {
      .card {
        height: 50%;
      }
    }
  }
}
</style>

<style>
.video #app {
  min-width: 100%;
  min-height: 100%;
}

@keyframes rotateRing {
  from {
    transform: rotate(0deg);
  }

  to {
    transform: rotate(360deg);
  }
}

@keyframes pulseDot {
  /* 0%, 100% {
    transform: translateX(-50%) scale(1);
    opacity: 1;
  }
  50% {
    transform: translateX(-50%) scale(1.5);
    opacity: 0.7;
  } */
}

@keyframes glowNumber {
  /* 0% {
    text-shadow: 0 0 10px rgba(0, 212, 255, 0.8);
  }
  100% {
    text-shadow: 0 0 20px rgba(0, 212, 255, 1), 0 0 30px rgba(0, 212, 255, 0.8);
  } */
}
</style>
